package com.ciban.smarthome.module.net.protocol;

import com.ciban.smarthome.common.utils.ConvertUtils;

public class Protocol {
	public static final int MODE_UDP = 0;
	public static final int MODE_TCP = 1;

	public static final int COMMON_OPEN = 2;
	public static final int COMMON_CLOSE = 0;
	public static final int COMMON_STOP = 1;

	public static final String CMD_QUERY_STATUS = "AA0B01004101000000F80A";

	/**
	 * 一般常用的控制命令
	 * 
	 * @param hostNo
	 * @param empNo
	 * @param opr
	 * @return
	 */
	public static String getNormalCmd(int hostNo, int empNo, int opr) {
		byte[] cmd = GetCmdInfo(hostNo, empNo, opr);
		cmd[cmd.length - 2] = (byte) getCheckNo(cmd);
		return ConvertUtils.bytes2hex(cmd);
	}

	/**
	 * 获取红外控制的命令
	 * 
	 * @param hostnum
	 * @param empno
	 * @param keycode
	 * @return
	 */
	public static String getIfCmd(int hostnum, int empno, int keycode) {
		byte[] cmd = GetCmdInfo(hostnum, empno, keycode, (byte) 1);
		cmd[cmd.length - 2] = (byte) getCheckNo(cmd);
		return ConvertUtils.bytes2hex(cmd);
	}

	/**
	 * 获取场景的相关命令
	 * 
	 * @param mainNo
	 * @param sceneNo
	 * @return
	 */
	public static String getSceneCmd(int mainNo, int sceneNo) {
		byte[] cmd = GetCmdInfo(mainNo, sceneNo);
		cmd[cmd.length - 2] = (byte) getCheckNo(cmd);
		return ConvertUtils.bytes2hex(cmd);
	}

	/**
	 * 获取校验码
	 * @param data
	 * @return
	 */
	private static int getCheckNo(byte[] data) {
		int chkSum = 0;
		for (int i = 0; i < data.length - 2; i++) {
			chkSum += convertByteToInt(data[i]);
		}
		chkSum = chkSum % 256;
		return chkSum;
	}

	private static int convertByteToInt(byte data) {
		return data >= 0 ? data : 256 + data;
	}

	/**
	 * 一般命令
	 * 
	 * @param mainNum
	 * @param DoNum
	 * @param opr
	 * @return
	 */
	private static byte[] GetCmdInfo(int mainNum, int DoNum, int opr) {
		byte[] info = new byte[11];

		info[0] = (byte) 0xAA;// 包头
		info[1] = 0x0B;// 长度
		info[2] = (byte) mainNum;// 主机号
		info[3] = 0x01;// 命令行
		info[4] = 0x41;// 表号
		info[5] = 0x01;// 行号
		info[6] = (byte) (DoNum - 1);// 设备编号,规定是这样的
		info[7] = 0x00;// 类型 灯的类型是固定的
		info[8] = (byte) opr;// 动作
		// info[9]=0x01;//校验
		info[10] = 0x0A;// 包尾

		return info;
	}

	/**
	 * 场景命令
	 * 
	 * @param mainNum
	 * @param SceneNum
	 * @return
	 */
	private static byte[] GetCmdInfo(int mainNum, int SceneNum) {
		byte[] info = new byte[11];

		info[0] = (byte) 0xAA;// 包头
		info[1] = 0x0B;// 长度
		info[2] = (byte) mainNum;// 主机号
		info[3] = 0x02; // 命令行
		info[4] = 0x11; // 表号
		info[5] = (byte) SceneNum; // 场景号
		info[6] = 0x00;// 保留
		info[7] = 0x00;// 保留
		info[8] = 0x01;// 保留
		// info[9]校验，在调用的地方有
		info[10] = 0x0A;// 包尾

		return info;
	}

	/**
	 * 根据动作键值得到命令内容字节，INFO标志位
	 * 
	 * @param mainNum
	 *            所在主机编号
	 * @param ptNum
	 *            所在红外编号
	 * @param keyNum
	 *            当前所按按键
	 * @param cmd
	 *            命令号 0x13学习键、0x12测试键
	 * @return
	 */
	private static byte[] GetCmdInfo(int mainNum, int ptNum, int keyNum,
			byte cmd) {
		byte Sum = 0, i;
		byte[] info = new byte[17];
		info[0] = (byte) 0XAA;
		info[1] = (byte) (info.length);
		info[2] = (byte) mainNum;// 目标主机号，也就是接收的主机号
		info[3] = (byte) (0x16);// 命令号 0x13学习键、0x12测试键 ==================这里有改动
		info[4] = 0x0c;
		info[5] = (byte) keyNum;
		info[6] = (byte) 0xdd;
		info[7] = (byte) (info[1] - 8);
		info[8] = (byte) ptNum;
		info[9] = 2;
		info[10] = 0x0C;// 命令转发
		info[11] = info[3]; // 命令号 学习键、测试键
		info[12] = (byte) keyNum;
		for (i = 6; i < info[1] - 4; i++)
			Sum += info[i];
		info[i++] = Sum;
		info[i] = 0x0A;
		info[16] = 0x0A;
		return info;
	}

	/**
	 * 红外获取室温协议
	 * 
	 * @param mainNum
	 * @param ptNum
	 * @return
	 */
	private byte[] getTemperature(int mainNum, int ptNum) {
		byte[] info = new byte[17];
		info[0] = (byte) 0xAA;
		info[1] = (byte) info.length;
		info[2] = (byte) (mainNum);// 主机号
		info[3] = 0x17;
		info[4] = 0x0C;
		info[5] = 0x0B;
		info[6] = (byte) 0xDD;
		info[7] = 0x09;
		info[8] = (byte) ptNum; // 编号
		info[9] = 0x02;
		info[10] = 0x0c;
		info[11] = 0x17;
		info[12] = 0x00;
		info[13] = 0x0C;
		info[14] = 0x0a;
		info[16] = 0x0a;
		return info;
	}
}
